package org.example.Polls;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.List;

import org.achartengine.ChartFactory;
import org.achartengine.GraphicalView;
import org.achartengine.model.CategorySeries;
import org.achartengine.renderer.DefaultRenderer;
import org.achartengine.renderer.SimpleSeriesRenderer;

import android.app.Activity;
import android.app.Dialog;
import android.content.Intent;
import android.graphics.Color;
import android.os.Bundle;
import android.text.format.DateFormat;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup.LayoutParams;
import android.widget.Button;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.TextView;

public class ViewPollDetailsActivity extends Activity {
	
	public static final String POLL_ID_EXTRA = "uVote.pollId";
	private static final String TAG = "ViewPollDetailsActivity";
	private static final int[] COLORS 
		= new int[] { Color.BLUE, Color.GREEN, Color.MAGENTA, Color.YELLOW, 
			          Color.CYAN, Color.RED, Color.WHITE, Color.GRAY};
	
	private static final int REQUEST_CODE_VOTE_ON_POLL = 1;
	private static final String DATE_FORMAT = "MMMM dd, yyyy h:mmaa";
	
	private static final int ADD_PARTICIPANT_DIALOG = 1;
	private static final int ADD_ITEM_DIALOG = 2;
	
	private TextView txtPollTitle;
	private TextView txtPollAdministrator;
	private TextView txtPollStatus;
	private Button btnVote;
	private LinearLayout layout;
	private GraphicalView mChartView;
	private CategorySeries mDataset;
	private DefaultRenderer mRenderer;
	private Long pollId;
	private Poll poll;

	/** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        
        setContentView(R.layout.view_poll_details);
        
        // Get the pollId passed to us
        Bundle extras = getIntent().getExtras();
        pollId = extras.getLong(POLL_ID_EXTRA);
        
        layout = (LinearLayout)findViewById(R.id.view_poll_details_layout);
        txtPollTitle = (TextView)findViewById(R.id.view_poll_details_title);
        txtPollAdministrator = (TextView)findViewById(R.id.view_poll_details_administrator);
        txtPollStatus = (TextView)findViewById(R.id.view_poll_details_status);
        btnVote = (Button)findViewById(R.id.view_poll_details_vote);
        
        btnVote.setOnClickListener(new OnClickListener() {
			public void onClick(View v) {
				Intent intent = new Intent(ViewPollDetailsActivity.this, VoteOnPollActivity.class);
				intent.putExtra(VoteOnPollActivity.POLL_ID_EXTRA, pollId);
				startActivityForResult(intent, REQUEST_CODE_VOTE_ON_POLL);
			}
		});
        
        // Get the poll (retrieves from the cache, or if not in the cache, delegates to pollService)
        try {
			poll = PollHelper.getPoll(pollId);
			Log.d(TAG, "got pollId="+pollId+", "+poll);
            txtPollTitle.setText(poll.getTitle());
            txtPollAdministrator.setText(poll.getAdministrator().getDisplayName(poll.getAnonymous()));
            txtPollStatus.setText(getPollStatus(poll));
		} catch (Exception e) {
			Log.d(TAG, "unable to get pollId="+pollId, e);
			ErrorDialogHelper.showErrorDialog(this, e.getMessage());
		}
    }
    
    @Override
	protected void onResume() {
		super.onResume();
		redrawChart();
	}
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
    	MenuInflater inflater = getMenuInflater();
    	inflater.inflate(R.menu.vote_menu, menu);
    	return true;
    }
    
    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
    	Intent intent;
    	// Handle item selection
    	switch(item.getItemId()) {
    	case R.id.refresh:
    		try {
        		poll = PollHelper.getPoll(pollId, true);
        		redrawChart();
    		} catch (Exception e) {
				Log.d(TAG, "caught exception refreshing poll", e);
				ErrorDialogHelper.showErrorDialog(this, e.getMessage());
    		}
    		return true;
    	case R.id.add_item:
    		showDialog(ADD_ITEM_DIALOG);
    		return true;
    	case R.id.add_participant:
    		showDialog(ADD_PARTICIPANT_DIALOG);
    		return true;
    	case R.id.vote:
    		intent = new Intent(this, VoteOnPollActivity.class);
    		Log.d(TAG, "pollId is " + pollId);
    		intent.putExtra(VoteOnPollActivity.POLL_ID_EXTRA, pollId);
    		startActivityForResult(intent,REQUEST_CODE_VOTE_ON_POLL);
    		return true;
    	default:
    		return super.onOptionsItemSelected(item);
    	}
    }

	@Override
	protected void onActivityResult(int requestCode, int resultCode, Intent data) {
		super.onActivityResult(requestCode, resultCode, data);
		switch (requestCode) {
		case REQUEST_CODE_VOTE_ON_POLL:
			if (resultCode == RESULT_OK) {
				try {
					Log.i(TAG, "Vote successful, refreshing poll from cache");
					poll = PollHelper.getPoll(pollId);
				} catch (Exception e) {
    				Log.d(TAG, "caught exception refreshing poll", e);
    				ErrorDialogHelper.showErrorDialog(this, e.getMessage());
				}
			}
			break;
		default:
			break;
		}
	}

	@Override
	protected Dialog onCreateDialog(int id) {
		switch(id) {
		case ADD_PARTICIPANT_DIALOG:
    		final Dialog addParticipantsDialog = new Dialog(this);
    		addParticipantsDialog.setContentView(R.layout.custom_add_participant_dialog);
    		addParticipantsDialog.setTitle("Add Participant by E-mail");
    		
    		final EditText txtParticipantEmail = (EditText) addParticipantsDialog.findViewById(R.id.text_email);
    		Button btnParticipantsAdd = (Button) addParticipantsDialog.findViewById(R.id.dialogadd);
    		btnParticipantsAdd.setOnClickListener(new OnClickListener() {
    			public void onClick(View v) {
    				if(txtParticipantEmail.getText().toString().length() != 0) {
    					Log.d(TAG, "Adding participant to poll: "+txtParticipantEmail.getText().toString());
    				}
    				try {
    					PollService pollService = DefaultServiceFactory.getInstance().createPollService();
    					RequestContext ctxt = RequestContext.getContext();
    					pollService.addParticipant(ctxt, txtParticipantEmail.getText().toString(), pollId);
    				} catch (Exception e) {
    					Log.e(TAG, "Unable to add participant", e);
    					ErrorDialogHelper.showErrorDialog(ViewPollDetailsActivity.this, e.getMessage());
    				}
    				addParticipantsDialog.dismiss();
    			}
    		});
    		Button dialogCancel = (Button) addParticipantsDialog.findViewById(R.id.dialogcancel);
    		dialogCancel.setOnClickListener(new OnClickListener() {
    			public void onClick(View v) {
    				addParticipantsDialog.dismiss();
    			}
    		});
    		return addParticipantsDialog;
		case ADD_ITEM_DIALOG:
    		final Dialog dialog = new Dialog(this);
    		dialog.setContentView(R.layout.custom_add_item_dialog);
    		dialog.setTitle("Add Poll Item");
    		TextView text = (TextView) dialog.findViewById(R.id.add_item_dialog_info);
    		text.setText("Please enter the poll option to add.");
    		final EditText eText = (EditText) dialog.findViewById(R.id.add_item_dialog_text);
    
    		Button dialogAdd = (Button) dialog.findViewById(R.id.add_item_dialog_add);
    		dialogAdd.setOnClickListener(new OnClickListener() {
    			public void onClick(View v) {
    				if(eText.getText().toString().length() != 0) {
    					Log.d(TAG, "Adding item to list: "+eText.getText().toString());
    				}
    				try {
    					PollService pollService = DefaultServiceFactory.getInstance().createPollService();
    					RequestContext ctxt = RequestContext.getContext();
    					pollService.addItem(ctxt, eText.getText().toString(), pollId);
    					// Need to refresh the poll since the items have changed.
    					poll = PollHelper.getPoll(pollId, true);
    					redrawChart();
    				} catch (Exception e) {
    					Log.e(TAG, "Unable to add item", e);
    					ErrorDialogHelper.showErrorDialog(ViewPollDetailsActivity.this, e.getMessage());
    				}
    				dialog.dismiss();
    			}
    		});
    		Button itemDialogCancel = (Button) dialog.findViewById(R.id.add_item_dialog_cancel);
    		itemDialogCancel.setOnClickListener(new OnClickListener() {
    			public void onClick(View v) {
    				dialog.dismiss();
    			}
    		});
    		return dialog;
		default:
			Log.w(TAG, "Unknown dialog in onCreateDialog");
    		return null;
		}
	}
	
	private void redrawChart() {
        mRenderer = new DefaultRenderer();
        mRenderer.setApplyBackgroundColor(true);
        mRenderer.setBackgroundColor(Color.argb(100, 50, 50, 50));
        mRenderer.setChartTitleTextSize(20);
        mRenderer.setLabelsTextSize(15);
        mRenderer.setLegendTextSize(15);
        mRenderer.setMargins(new int[] { 20, 30, 15, 0 });
        mRenderer.setZoomButtonsVisible(true);
                    
		mDataset = new CategorySeries(poll.getTitle());
        List<PollItem> pollItemList = new ArrayList<PollItem>(poll.getItems());
        Collections.sort(pollItemList, new Comparator<PollItem>(){
			public int compare(PollItem lhs, PollItem rhs) {
				return lhs.getText().toLowerCase().compareTo(rhs.getText().toLowerCase());
			}
        });
		int i=0;
		for (PollItem item : pollItemList) {
			Log.i(TAG, item.getText()+": "+item.getNumVotes());
			String itemText = item.getText() + " ("+item.getNumVotes()+")";
			mDataset.add(itemText, item.getNumVotes());
        	SimpleSeriesRenderer r = new SimpleSeriesRenderer();
        	r.setDisplayChartValues(true);
        	r.setColor(COLORS[i%COLORS.length]);
        	i++;
        	mRenderer.addSeriesRenderer(r);
		}
            		
		// Create the graph.
	    layout.removeView(mChartView);
	    mChartView = ChartFactory.getPieChartView(this, mDataset, mRenderer);
	    layout.addView(mChartView, new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT));
	}

	public String getPollStatus(Poll poll) {
        String status;
        Date now = new Date();
        if (poll.getStartDate().after(now)) {
        	status = "Starts on "+DateFormat.format(DATE_FORMAT, poll.getStartDate());
        } else if (poll.getEndDate().before(now)) {
        	status = "Finished at "+DateFormat.format(DATE_FORMAT, poll.getEndDate());
        } else {
        	status = "Active until "+DateFormat.format(DATE_FORMAT, poll.getEndDate());
        }
        return status;
    }
    
}
